#!/usr/bin/python

import cgi
import logging

from google.appengine.api import users
from google.appengine.ext import db
from google.appengine.ext import webapp
from google.appengine.ext.webapp.util import run_wsgi_app

from hips import datastore
from hips import serialization
from hips import translator
from hips.handlers import query
from hips.scheduling import constraint  # TODO Proper error logging


class ContextRootHandler(webapp.RequestHandler):
  """Called on web app startup to query.Query for initial context."""

  def get(self):
    # TODO Return models instead
    user = users.get_current_user()
    logging.info("Context root")
    context = {}
    if user:
      context["login"] = user.email()
    else:
      logging.info("No user")
      context["login"] = "none"
    
    logging.info("Request for context root: %s" % str(context))
    self.response.out.write(str(context))

  def post(self):
    pass


class AssignDoctorsHandler(webapp.RequestHandler):
  """Called from scheduling to create schedules."""

  def get(self):
    schedule_key = db.Key(self.request.get("schedule"))
    schedule_models = query.QueryForSchedule(schedule_key)
    problem = translator.CreateHipsSchedulingProblem(
        schedule_models.OfType(datastore.Schedule)[0],
        schedule_models.OfType(datastore.ScheduleBlock),
        schedule_models.OfType(datastore.DoctorConstraint))
    solution = problem.Solve()
    logging.info("Final solution:")
    if solution:
      logging.info(solution)
      logging.info(solution.FormatSolutionAsString())
      doctors = query.QueryForModels("SELECT * FROM Doctor WHERE "
          "institution = :institution", self.request).All()
      doctors_map = {}
      for doctor in doctors:
        doctors_map[doctor.name] = doctor
      solution_models = translator.CreateScheduleSolutionModels(
          schedule_models.OfType(datastore.Schedule)[0],
          schedule_models.OfType(datastore.ScheduleBlock),
          solution, doctors_map)
      json_value = serialization.WriteModelListToString(solution_models)
      self.response.out.write(json_value)
      logging.info("SUCCESS")
    else:
      logging.info("No solutions found")
      self.response.out.write("No solutions found")
    logging.info("Iterations: %d" % problem.iterations)
    #logging.info("Rejection reasons:")
    #for k, v in constraint.GetConstraintRejectionReasons().iteritems():
    #  logging.info("%-40s %7d" % (k, v))

  def post(self):
    pass
